﻿namespace MDXStudio.QueryEditor
{
    using System;
    using System.Collections;
    using System.Drawing;
    using System.Windows.Forms;

    internal class WigglyLinesPainter : NativeWindow
    {
        private Bitmap bitmap;
        private Graphics bufferGraphics;
        private MDXStudio.QueryEditor.WigglyLines m_WigglyLines = new MDXStudio.QueryEditor.WigglyLines();
        private MdxEditor parentTextBox;
        private Graphics textBoxGraphics;

        internal WigglyLinesPainter(MdxEditor textBox)
        {
            this.parentTextBox = textBox;
            this.bitmap = new Bitmap(textBox.Width, textBox.Height);
            this.bufferGraphics = Graphics.FromImage(this.bitmap);
            this.bufferGraphics.Clip = new Region(textBox.ClientRectangle);
            this.textBoxGraphics = Graphics.FromHwnd(textBox.Handle);
            base.AssignHandle(this.parentTextBox.Handle);
        }

        internal void AddWigglyLine(WigglyLine wl)
        {
            if (this.m_WigglyLines != null)
            {
                this.m_WigglyLines.Add(wl);
            }
        }

        internal void ClearWigglyLines()
        {
            if (this.m_WigglyLines != null)
            {
                this.m_WigglyLines.Clear();
            }
        }

        private void CustomPaint()
        {
            int firstVisibleLine = TextBoxAPIHelper.GetFirstVisibleLine(this.parentTextBox);
            firstVisibleLine = TextBoxAPIHelper.GetLineIndex(this.parentTextBox, firstVisibleLine);
            this.bufferGraphics.Clear(Color.Transparent);
            foreach (WigglyLine line in this.m_WigglyLines)
            {
                Point start = TextBoxAPIHelper.PosFromChar(this.parentTextBox, line.StartChar);
                Point end = TextBoxAPIHelper.PosFromChar(this.parentTextBox, line.EndChar);
                end.X++;
                start.Y += TextBoxAPIHelper.GetBaselineOffsetAtCharIndex(this.parentTextBox, line.StartChar);
                end.Y += TextBoxAPIHelper.GetBaselineOffsetAtCharIndex(this.parentTextBox, line.EndChar);
                this.DrawWave(start, end);
            }
            this.textBoxGraphics.DrawImageUnscaled(this.bitmap, 0, 0);
        }

        private void DrawWave(Point start, Point end)
        {
            Pen red = Pens.Red;
            if ((end.X - start.X) > 4)
            {
                ArrayList list = new ArrayList();
                for (int i = start.X; i <= (end.X - 2); i += 4)
                {
                    list.Add(new Point(i, start.Y));
                    list.Add(new Point(i + 2, start.Y + 2));
                }
                Point[] points = (Point[]) list.ToArray(typeof(Point));
                this.bufferGraphics.DrawLines(red, points);
            }
            else
            {
                this.bufferGraphics.DrawLine(red, start, end);
            }
        }

        protected override void WndProc(ref Message m)
        {
            if ((this.m_WigglyLines == null) || (this.m_WigglyLines.Count == 0))
            {
                base.WndProc(ref m);
            }
            else if (m.Msg == 15)
            {
                this.parentTextBox.Invalidate();
                base.WndProc(ref m);
                this.CustomPaint();
            }
            else
            {
                base.WndProc(ref m);
            }
        }

        internal MDXStudio.QueryEditor.WigglyLines WigglyLines
        {
            get
            {
                return this.m_WigglyLines;
            }
            set
            {
                this.m_WigglyLines = value;
            }
        }
    }
}

